package com.fz.security.provider;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.fz.common.Global;
import com.fz.common.ResultCode;
import com.fz.entity.member.Member;
import com.fz.mapper.member.MemberMapper;
import com.fz.security.AuthExceptionDto;
import com.fz.security.tokens.MobileCodeAuthenticationToken;
import com.fz.utils.JacksonUtils;
import com.fz.utils.RedisUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;
import java.util.HashSet;
import java.util.Set;
@Component
public class MobileCodeAuthenticationProvider implements AuthenticationProvider {

    @Resource
    private RedisUtil redisUtil;
    @Resource
    private MemberMapper memberMapper;

    private final Logger logger = LoggerFactory.getLogger(MobileCodeAuthenticationProvider.class.getSimpleName());
    /**
     * @方法描述: 验证手机号验证码登录
     * @参数:
     * @返回值:
     * @创建人: I am God
     * @创建时间:: 2021/2/24
     */
    public Authentication authenticate(Authentication authentication) throws AuthenticationException {
        //获取手机号
        String mobile = (String) authentication.getPrincipal();
        //获取验证码
        String code = (String) authentication.getCredentials();
        logger.info("当前手机号登录参数,mobile:{}, code:{}", mobile, code);
        //判断验证码是否正确
        String captcha = "";
        String key = Global.LOGIN_MSG_CODE_KEY + mobile;
        if (redisUtil.hasKey(key)) {
            captcha = (String) redisUtil.get(key);
        }
        if (!code.equals(captcha)) {
            throw new BadCredentialsException(JacksonUtils.obj2String(new AuthExceptionDto(ResultCode.MSG_CODE_ERROR.getResultCode(), ResultCode.MSG_CODE_ERROR.getMessage())));
        }
        //查询手机号是否存在，若不存在则该手机号代表注册的新用户
        LambdaQueryWrapper<Member> lambdaQueryWrapper = Wrappers.lambdaQuery();
        lambdaQueryWrapper.eq(Member::getMobilePhone,mobile);
        Member member = memberMapper.selectOne(lambdaQueryWrapper);
        if (null == member) {
            //注册用户(用户信息只有手机号信息)
            member = new Member();
            member.setMobilePhone(mobile);
            memberMapper.insert(member);
        }
        UsernamePasswordAuthenticationToken result = new UsernamePasswordAuthenticationToken(member.getMobilePhone(), code, listUserGrantedAuthorities(member.getUid()));
        result.setDetails(member);
        return result;
    }

    @Override
    public boolean supports(Class<?> authentication) {
        return (MobileCodeAuthenticationToken.class.isAssignableFrom(authentication));
    }

    private Set<GrantedAuthority> listUserGrantedAuthorities(Integer uid) {
        Set<GrantedAuthority> authorities = new HashSet<GrantedAuthority>();
        return authorities;
    }
}
